<?php

namespace Kangcg\Application\Security;

/**
 * Class Openssl
 * @package Kang\Libs\Helper\Security
 */
class Hash implements SecurityInterface
{
    /**
     * @param array $config
     * @param string key 密匙
     * @param string iv 必须16位
     * @param string method aes-256-cbc
     * @param int option //补位方式  OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING OPENSSL_RAW_DATA|OPENSSL_ZERO_PADDING.
     */
    public function __construct(array $config)
    {
        $this->init($config);
    }

    /**
     * 要加密的字符
     * @param string | array $encrypted
     * @return bool|false|string
     */
    public function encode($data, bool $isUsePublic = false)
    {
        $data = is_array($data) ? json_encode($data) : $data;
        $encrypted = '';
        $length = strlen($data);
        $shift = $this->_config['option'];
        for ($i = 0; $i < $length; $i++) {
            $charCode = ord($data[$i]);
            $encryptedCharCode = $charCode + $shift;
            $encrypted .= chr($encryptedCharCode);
        }

        return base64_encode($encrypted);
    }

    /**
     * 获取解密结果
     * @param string $encrypted
     * @return bool|false|string
     */
    public function decode(string $encrypted, $isUsePublic = true)
    {
        $encryptedString = base64_decode($encrypted);
        $decrypted = '';
        $shift = 3;
        $len = strlen($encryptedString);
        for ($i = 0; $i < $len; $i++) {
            $charCode = ord($encryptedString[$i]);
            $decryptedCharCode = $charCode - $shift;
            $decrypted .= chr($decryptedCharCode);
        }

        return $decrypted;
    }

    public function sign(string $str)
    {
        return md5($str);
    }

    /**
     * @return string
     */
    public function getEncryption(): string
    {
        return 'hash';
    }

    /**
     * @param null $key
     * @return array|mixed|string
     */
    public function getConfig($key = null)
    {
        return $key === null ? $this->_config : ($this->_config[$key] ?? '');
    }

    /**
     * @param array $config
     * @param string key 密匙
     * @param string iv 必须16位
     * @param string method
     * @param int option //补位方式  OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING OPENSSL_RAW_DATA|OPENSSL_ZERO_PADDING.
     * @return Openssl
     */
    public static function getInstall(array $config)
    {
        if (self::$_install === null) {
            self::$_install = new self($config);
        }

        return self::$_install;
    }

    /**
     * @param array $config
     * @param string key 密匙
     * @param string iv 必须16位
     * @param string method aes-256-cbc
     * @param int option //补位方式  OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING OPENSSL_RAW_DATA|OPENSSL_ZERO_PADDING.
     * @return $this
     */
    public function init(array $config)
    {
        $this->_config['option'] = $config['option'] ?? 3;
        return $this;
    }

    private function setError($error)
    {
        $this->_error = $error;
        return false;
    }

    public function getError()
    {
        return $this->_error;
    }

    private $_error = null;
    private $_config = null;
    private static $_install = null;
}
